//$Id: HibernateInterceptor.java,v 1.2.2.3 2007/01/03 22:19:28 gilmar Exp $
package br.com.cefetrn.apoena.interceptor;

import javax.swing.AbstractAction;

import org.apache.commons.lang.StringUtils;
import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
import org.hibernate.HibernateException;

import br.com.cefetrn.apoena.view.action.AxActionAPOENA;
import br.com.cefetrn.apoena.view.component.HibernateSession;

import com.opensymphony.xwork.Action;
import com.opensymphony.xwork.ActionInvocation;
import com.opensymphony.xwork.interceptor.Interceptor;

/**
 * @author Gavin King
 * @author Gilmar
 */
public class HibernateInterceptor implements Interceptor {
	
	private static final Log LOG = LogFactory.getLog(HibernateInterceptor.class);
	
	private static final String STREAM_PROBLEM_WEBWORK = "com.opensymphony.webwork.dispatcher.StreamResult.doExecute";
	
	public void destroy() {}

	public void init() {}

	public String intercept(ActionInvocation invocation) throws Exception {
		Action action = (Action) invocation.getAction();
		if ( !(action instanceof AbstractAction) ) return invocation.invoke();
		
		LOG.debug("((AbstractAction) action).getHibernateSession()");
		HibernateSession hs = ((AxActionAPOENA) action).getHibernateSession();
		
		try {
			LOG.debug("invocating");
			return invocation.invoke();
		}
		
		// Note that all the cleanup is done
		// after the view is rendered, so we
		// have an open session in the view
		catch(NullPointerException e){
			
			try{	
			
				if(StringUtils.contains(e.getStackTrace()[0].toString(),STREAM_PROBLEM_WEBWORK))
					return Action.SUCCESS;//semAcao
				else
					throw e;
				
			}catch(NullPointerException x){
				LOG.error("NullPointerException ", e);
				return Action.ERROR;
			}
				
		}
		catch (Exception e) {	
			hs.setRollBackOnly(true);
			if (e instanceof HibernateException) {
				LOG.error("HibernateException in execute()", e);
				return Action.ERROR;
			}
			else {
				LOG.error("Exception in execute()", e);
				throw e;
			}
		}
		
		finally {
			try {
				LOG.debug("disposing session");
				hs.disposeSession();
			}
			catch (HibernateException e) {
				LOG.error("HibernateException in dispose()", e);
				return Action.ERROR;
			}
		}
	}

}
